<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>语音助手</title>
    <style>
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }
        
        textarea {
            border: 0;
            padding: 0;
            outline: none;
            width: 100%;
            height: 100%;
        }
        
        html {
            width: 100%;
            background-color: aliceblue;
        }
        
        .contain {
            margin: 0 auto;
            width: 1120px;
            height: 320px;
            /* background-color: gray; */
            display: grid;
            grid-template-rows: 1fr 3fr 1fr;
        }
        
        .content-text {
            font-size: 18px;
            font-family: arial, sans-serif;
            letter-spacing: 2px;
        }
        
        .top {
            font-family: arial, sans-serif;
            font-weight: 700;
            color: #46beef;
            letter-spacing: 5px;
            display: flex;
            flex-direction: column;
            justify-content: flex-end;
            padding-left: 21px;
            padding-bottom: 12px;
        }
        
        .middle {
            border-radius: 15px;
            border: 2px solid #ebebeb;
            background-color: #fff;
            box-shadow: 0px 0px 3px 2px #c9c9c9;
            padding: 15px;
        }
        
        .content {
            display: inline-block;
            width: 100%;
            height: 100%;
        }
        
        .bottom {
            display: flex;
            justify-content: space-between;
        }
        
        .text-speech {
            width: 190px;
            height: 35px;
            background-color: #e6a23c;
            text-align: center;
            border-radius: 10px;
            margin-top: 20px;
            margin-left: 30px;
            color: #fff;
            line-height: 35px;
            letter-spacing: 2px;
        }
        
        .text-speech:hover {
            cursor: pointer;
            background-color: #ebb563;
        }
        
        .bottom-right {
            display: flex;
            justify-content: flex-end;
            margin-top: 20px;
            margin-right: 20px;
        }
        
        .send {
            width: 108px;
            height: 35px;
            letter-spacing: 2px;
            border-radius: 10px;
            background-color: #409eff;
            text-align: center;
            line-height: 35px;
            color: #fff;
        }
        
        .send:hover {
            background-color: #66b1ff;
            cursor: pointer;
        }
        
        .num {
            width: 93px;
            height: 35px;
            margin-right: 20px;
            text-align: center;
            line-height: 35px;
        }
        
        .num-color {
            color: red;
        }
        
        .speak {
            height: 35px;
            display: flex;
            align-items: center;
            color: #fff;
        }
        
        .speak-start {
            width: 108px;
            height: 100%;
            background-color: #67c23a;
            text-align: center;
            line-height: 35px;
            margin-right: 20px;
            border-radius: 10px;
        }
        
        .speak-start:hover {
            background-color: #85ce61;
            cursor: pointer;
        }
        
        .speak-stop {
            width: 108px;
            height: 100%;
            text-align: center;
            line-height: 35px;
            background-color: #f56c6c;
            border-radius: 10px;
        }
        
        .speak-stop:hover {
            background-color: #f78989;
            cursor: pointer;
        }
    </style>
</head>

<body>
    <div class="contain">
        <div class="top">
            <span>语音识别小助手（注：该功能仅支持特定的浏览器）</span>
        </div>
        <div class="middle">
            <!-- style="resize: none" ：禁止修改边框大小 -->
            <span class="content"><textarea class="content-text" type="text" placeholder="说点什么···"
                    style="resize: none"></textarea></span>
        </div>
        <div class="bottom">
            <div class="bottom-left">
                <div class="text-speech">文字转换为语音播放</div>
            </div>
            <div class="bottom-right">
                <div class="speak">
                    <div class="speak-start">开始语音</div>
                    <div class="speak-stop">结束语音</div>
                </div>
                <div class="num"> <span class="num-color">0</span> / 200</div>
                <div class="send">发送</div>
            </div>

        </div>
    </div>
    <script>
        // 引入 web speakAPI
        const SpeechRecognition = window.SpeechRecognition || window.webkitSpeechRecognition;
        const recognition = new SpeechRecognition;
        recognition.continuous = true; // 持续识别
        recognition.interimResults = true; // 中间结果可用
        recognition.lang = "zh-CN"; // 支持普通话 "zh-HK"
        const utterance = new SpeechSynthesisUtterance();
        utterance.volume = 1;
        utterance.lang = "zh-CN";

        let state = true; // 用来判断
        var contentText = document.querySelector(".content-text");
        var speakStart = document.querySelector(".speak-start");
        var speakStop = document.querySelector(".speak-stop");
        var numText = document.querySelector(".num-color");
        var send = document.querySelector(".send");
        var textSpeech = document.querySelector(".text-speech");
        setInterval(() => { // 目的：在于监听如果手动删除了字数，可以检测长度是否可以继续语音识别
            if (contentText.value.length > 200) {
                state = false
                recognition.stop()
            } else {
                state = true
                numText.innerHTML = contentText.value.length
            }
        }, 1000);
        speakStart.addEventListener("click", () => {
            if (state) {
                recognition.start();
            };
        });
        if (state) {
            recognition.addEventListener('result', (event) => {
                // 监听到的值都是每一个数组， 通过使用 Map 将转换为文本给捞起来 
                const transcript = Array.from(event.results)
                    .map(result => result[0])
                    .map(result => result.transcript)
                    .join('');
                if (transcript.length > 200) {
                    state = false;
                    recognition.stop()
                    alert("内容已超出200！")
                    return
                };
                contentText.value = transcript;
                numText.innerHTML = contentText.value.length;
            });

        }

        textSpeech.addEventListener("click", () => {

            // console.log(contentText.value);
            if (contentText.value.length <= 0) {
                alert("没有文本")
                return
            }
            utterance.text = contentText.value;
            speechSynthesis.speak(utterance);
        })
        speakStop.addEventListener("click", () => {
            recognition.stop();
        });
        send.addEventListener("click", () => {
            alert(`已发送：${contentText.value}`);
        })
    </script>
</body>

</html>